
/**
 * 数组转树
 * @param {Array} data 源数据数组
 * @param {Object} [options]
 * @param {string} [options.idKey=id] id的属性名
 * @param {string} [options.parentIdKey=parentId] 父节点id的属性名
 * @param {string} [options.childrenArrayKey=children] 孩子数组的属性名
 * @returns {Array} 树数组
 */
export function convertTree(data, options) {
  if (!Array.isArray(data)) {
    throw new Error('data必须是数组')
  }
  if (data.length === 0) {
    return []
  }

  options = options || {}
  if (Object.prototype.toString.call(options) !== '[object Object]') {
    throw new Error('options必须是对象')
  }

  options.idKey = options.idKey || 'id'
  options.parentIdKey = options.parentIdKey || 'parentId'
  options.childrenArrayKey = options.childrenArrayKey || 'children'

  if (!(options.idKey in data[0])) {
    throw new Error('没有属性名为' + options.idKey + '的idKey')
  }
  if (!(options.parentIdKey in data[0])) {
    throw new Error('没有属性名为' + options.parentIdKey + '的parentIdKey')
  }

  const tree = []

  // id的索引表
  const idMap = data.reduce((total, currentValue, currentIndex) => {
    total[currentValue[options.idKey]] = currentIndex
    return total
  }, {})
  // 构造树结构
  data.forEach(val => {
    if (val[options.parentIdKey]) {
      const parent = data[idMap[val[options.parentIdKey]]]
      parent[options.childrenArrayKey] = [...(parent[options.childrenArrayKey] || []), val]
    } else {
      tree.push(val)
    }
  })
  return tree
}
